home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Collection of Tools & Utilities
/
Collection of Tools and Utilities.iso
/
dskut
/
record11.zip
/
RECORDER.ASM
< prev
next >
Wrap
Assembly Source File
|
1988-05-17
|
22KB
|
746 lines
Page 60,132
;----------------------------------------------------------------------
; RECORDER.ASM - A resident program which counts file operations.
; Run it once to install and initialize it. Run it again later to
; view a list of files which have been accessed. The table
; shows how many disk accesses have been made while reading and
; writing to the file.
;
; SYNTAX: RECORDER [n] [/R]
; USE n to specify the maximum number of files (default=200)
; Use /R to reset the file table.
;----------------------------------------------------------------------
CSEG SEGMENT
ASSUME CS:CSEG,DS:NOTHING
ORG 100H ;Beginning for .COM programs
START: JMP INITIALIZE ;Initialization code is at end
;-----------------------------------------------------------------------
; Data area used by this program
;-----------------------------------------------------------------------
COPYRIGHT DB "RECORDER 1.0 (c) 1988 Ziff Communications Co."
PROGRAMMER DB 13,10,"PC Magazine ",254," Tom Kihlken$",1AH
FULL_MESS DB "*Table is saturated*$"
OLDINT21 DD ? ;Old DOS function interrupt vector
OLDINT13 DD ? ;Old BIOS disk I/O interrupt vector
NUM_FILES DW 200 ;Default size of the table
FILE_TABLE_END DW ?
LAST_FILE DW ?
LAST_HANDLE DW ?
;--to help count spaces-012345678901234567890123456789012345678901-----
HEADER DB " File Name Total Read Write EXEC$"
CURRENT_FILE DB 11 DUP (?)
CURRENT_HANDLE DW ?
FUNCTION_ID DW ?
BUSY_FLAG DB 0
BIOS_IO_COUNT DW 0 ;Counts disk accesses made by BIOS
HANDLE_TABLE EQU OFFSET INITIALIZE
FILE_TABLE EQU HANDLE_TABLE + NUM_HANDLES * 4
NUM_HANDLES EQU 30
ENTRY_SIZE EQU 20
;-----------------------------------------------------------------------
; Interrupt 13 (Diskette I/O) This routine counts disk sector accesses.
;-----------------------------------------------------------------------
NEWINT13 PROC FAR
ASSUME DS:NOTHING, ES:NOTHING
CMP AH,2 ;Is function lower than 2?
JB DONT_COUNT ;If yes, then ignore it
CMP AH,4 ;Is function higher than 4?
JA DONT_COUNT ;If yes, then ignore it
INC CS:BIOS_IO_COUNT;Add sectors count to total
DONT_COUNT:
JMP CS:OLDINT13 ;Continue with disk interrupt
NEWINT13 ENDP
;-----------------------------------------------------------------------
; Interrupt 21 (DOS functions) This routine counts file accesses.
;-----------------------------------------------------------------------
NEWINT21 PROC FAR
ASSUME DS:NOTHING, ES:NOTHING
PUSHF ;Save callers flags
STI ;Get interrupts back on
CMP CS:BUSY_FLAG,0 ;Are we busy now?
JNE OLD_DOS ;If busy, just pass it to DOS
CMP AH,4BH ;Is it the EXEC function?
JE EXEC ;Handle EXEC specially
CMP AH,0EH ;Is it below 0EH?
JBE OLD_DOS ;If yes, ignore it
CMP AH,31H ;Is it TSR function?
JE OLD_DOS ;Dont intercept this call
CMP AH,45H ;Is it above 45H?
JB INTERCEPT_IT ;If yes, then ignore it
OLD_DOS:
POPF ;Recover callers flags
CLI
JMP CS:OLDINT21 ;Allow interrupt to proceed
EXEC:
PUSH AX ;Save these registers
PUSH BX
PUSH CX
PUSH SI
PUSH DI
PUSH DS
PUSH ES
MOV CS:BUSY_FLAG,1 ;Set the busy flag
MOV SI,OFFSET PARSE_STRING ;Point to parse routine
CALL ENTER_FILENAME ;Search file table for the file
JC EXEC_CONTINUE
INC WORD PTR DS:[SI+12]
INC WORD PTR DS:[SI+18]
EXEC_CONTINUE:
MOV CS:BUSY_FLAG,0 ;Not busy any more
POP ES ;Restore the registers
POP DS
POP DI
POP SI
POP CX
POP BX
POP AX
JMP OLD_DOS
INTERCEPT_IT:
MOV BUSY_FLAG,1 ;Ignore any other calls
MOV FUNCTION_ID,AX ;Save the function ident.,
MOV BIOS_IO_COUNT,0
CLI
CALL CS:OLDINT21 ;Do the DOS function
STI ;Reenable interrupts
PUSHF ;Save DOS result flags
PUSH AX ;Save these registers
PUSH BX
PUSH CX
PUSH DX
PUSH SI
PUSH DI
PUSH DS
PUSH ES
JNC CHECK_FUNCTION ;If no error, continue
JMP POP_RET ;Otherwise just return
CHECK_FUNCTION:
MOV CX,FUNCTION_ID
SUB CH,0FH ;Is it 0Fh?
JZ READ_FCB
DEC CH ;Is it 10h?
JZ WRITE_FCB
SUB CH,4 ;Is it 14h?
JZ READ_FCB
DEC CH ;Is it 15h?
JZ WRITE_FCB
DEC CH ;Is it 16h?
JZ READ_FCB
SUB CH,0BH ;Is it 21h?
JZ READ_FCB
DEC CH ;Is it 22h?
JZ WRITE_FCB
DEC CH ;Is it 23h?
JZ READ_FCB
SUB CH,4 ;Is it 27h?
JZ READ_FCB
DEC CH ;Is it 28h?
JZ WRITE_FCB
JMP SHORT NOT_FCB_FUNCTN
READ_FCB:
MOV BX,14 ;Index for the read column
JMP SHORT INC_FCB_COUNT
WRITE_FCB:
MOV BX,16 ;Index for the write column
INC_FCB_COUNT:
MOV SI,OFFSET PARSE_FCB
CALL ENTER_FILENAME ;Search file table for the file
JC JUMP_POP_RET ;Quit if file not in table
MOV AX,BIOS_IO_COUNT;This many disk operations made
ADD CS:[SI][BX],AX ;Add it to the indexed column
ADD CS:[SI+12],AX ;Add it to the total
JMP POP_RET
; If it was not a FCB function, see if it was handle I/O
NOT_FCB_FUNCTN:
SUB CH,14H ;Is it 3Ch?
JE NEW_HANDLE
DEC CH ;Is it 3Dh?
JE NEW_HANDLE
DEC CH ;Is it 3Eh?
JE WRITE_HANDLE
DEC CH ;Is it 3Fh?
JE READ_HANDLE
DEC CH ;Is it 40h?
JE WRITE_HANDLE
SUB CH,2 ;Is it 42h?
JE READ_HANDLE
SUB CH,2 ;Is it 44h?
JE IO_CONTROL
JMP POP_RET
NEW_HANDLE:
CMP AX,5 ;Is it a standard handle?
JGE GOOD_HANDLE ;If not, then record it
JUMP_POP_RET:
JMP POP_RET ;Jump to the return
READ_HANDLE:
MOV CX,14 ;Index for the read column
JMP SHORT INC_DEV_COUNT
IO_CONTROL:
CMP CL,2 ;Is it a read request?
JE READ_HANDLE ;Treat it as a read
CMP CL,3 ;Is it a write request?
JNE JUMP_POP_RET ;If not read or write, ignore it
WRITE_HANDLE:
MOV CX,16 ;Index for the write column
INC_DEV_COUNT:
CMP BX,5 ;Is it a standard handle?
JB JUMP_POP_RET ;If it is, then ignore it
PUSH CX ;Put index on the stack
; Now search the handle table for the handle in BX.
CALL ADD_PSP ;Add in the current PSP segment
MOV DI,HANDLE_TABLE ;Point to the handle table
MOV CX,NUM_HANDLES ;Search the entire table
HANDLE_LOOP:
CMP BX,CS:[DI] ;Is it a match?
JE HANDLE_MATCH ;If it is, we've found it
ADD DI,4 ;If not, look at next entry
LOOP HANDLE_LOOP
POP BX ;Restore the stack
JMP SHORT POP_RET ;Return if handle was not found
; If the handle is being closed, then the entry is deleted.
HANDLE_MATCH:
CMP BYTE PTR FUNCTION_ID+1,3EH ;Closing this file?
JNE NOT_CLOSE
MOV WORD PTR CS:[DI],0
NOT_CLOSE:
MOV DI,CS:[DI+2] ;Get pointer to file table entry
POP BX ;Get the index back
MOV AX,BIOS_IO_COUNT ;Get the sector count
ADD CS:[DI][BX],AX ;Add it to selected column
ADD CS:[DI+12],AX ;And also to the total column
JMP SHORT POP_RET
GOOD_HANDLE:
MOV CURRENT_HANDLE,AX ;Save the handle
MOV SI,OFFSET PARSE_STRING ;Point to parse routine
CALL ENTER_FILENAME ;Add the file to the table
JC JUMP_POP_RET ;If table is full, return
MOV AX,BIOS_IO_COUNT;Get number of sectors
ADD DS:[SI+12],AX ;Add to the total column
ADD DS:[SI+14],AX ;Add to the read column
; Now enter this new handle to the handle table
MOV DI,LAST_HANDLE ;Get location of last entry
ADD DI,4 ;Advance it one position
CMP DI,HANDLE_TABLE+NUM_HANDLES*4
JNE KEEP_GOING
MOV DI,HANDLE_TABLE
KEEP_GOING:
MOV LAST_HANDLE,DI ;Now this is the last handle
MOV BX,CURRENT_HANDLE ;Get handle back
CALL ADD_PSP ;Add in the current PSP segment
MOV CS:[DI],BX ;Store the handle
MOV CS:[DI+2],SI ;Store location in file table
POP_RET:
MOV CS:BUSY_FLAG,0 ;Not busy any more
POP ES ;Restore all registers
POP DS
POP DI
POP SI
POP DX
POP CX
POP BX
POP AX
POPF ;Recover DOS result flags
STI ;Return with interrupts on
RET 2 ;Return with these flags
NEWINT21 ENDP
;-----------------------------------------------------------------------
; ENTER_FILENAME adds the file at DS:DX to the table.
; It returns with DS:SI pointing to the entry. If CF=1, then the name
; was not in the table and no more entries could be added.
;-----------------------------------------------------------------------
ASSUME DS:NOTHING, ES: